In [1]:
%matplotlib ipympl

import numpy as np
import matplotlib.pyplot as plt
In [2]:
# read point clouds data from txt file, each row is a point (x,y,z)
point_clouds = np.loadtxt('tls_points.txt')
print(f"Total points in point cloud: {point_clouds.shape[0]}")
Total points in point cloud: 177748

Keep only the tree¶

In [3]:
# plot the point clouds interactively
fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')
ax.scatter(point_clouds[:,0], point_clouds[:,1], point_clouds[:,2], s=1)
ax.set_xlabel('X')
ax.set_ylabel('Y')
ax.set_zlabel('Z')
plt.show()
Figure
No description has been provided for this image
In [4]:
# remove all z points below a certain threshold (e.g., ground level)
# plot histogram of z values to determine threshold
# new plot
fig = plt.figure()
plt.hist(point_clouds[:,2], bins=100, range=(0, 0.1))
plt.xlabel('Z value')
plt.ylabel('Frequency')
plt.title('Histogram of Z values in Point Cloud')
plt.show()
Figure
No description has been provided for this image
In [5]:
# remove all z_points below 0.02
z_threshold = 0.05
filtered_points = point_clouds[point_clouds[:,2] > z_threshold]
print(f"Points after removing ground level: {filtered_points.shape[0]}")    
# plot filtered point clouds
fig = plt.figure(figsize=(10, 8))
ax = fig.add_subplot(111, projection='3d')
ax.scatter(filtered_points[:,0], filtered_points[:,1], filtered_points[:,2], s=1)
ax.set_xlabel('X')
ax.set_ylabel('Y')
ax.set_zlabel('Z')
plt.show()
Points after removing ground level: 30960
Figure
No description has been provided for this image

Keep only the tree half which faces the LiDAR scanner¶

In [6]:
# plot histogram on Y values 
fig = plt.figure()
plt.hist(filtered_points[:,1], bins=100)
# plot mode
mode_y = 15
plt.axvline(mode_y, color='r', linestyle='dashed', linewidth=1)
plt.xlabel('Y value')
plt.ylabel('Frequency')
plt.title('Histogram of Y values in Filtered Point Cloud')
plt.show()
Figure
No description has been provided for this image
In [7]:
# filter out all points with y > mode_y
y_threshold = mode_y + 0.1 # add some margin in case some leaves get cut off
filtered_points = filtered_points[filtered_points[:,1] < y_threshold]
print(f"Points after removing high Y values: {filtered_points.shape[0]}")    
# plot final point clouds
fig = plt.figure(figsize=(10, 8))
ax = fig.add_subplot(111, projection='3d')
ax.scatter(filtered_points[:,0], filtered_points[:,1], filtered_points[:,2], s=1)
ax.set_xlabel('X')
ax.set_ylabel('Y')
ax.set_zlabel('Z')
plt.show()
Points after removing high Y values: 24507
Figure
No description has been provided for this image
In [8]:
# down sampling the point clouds for faster processing
sample_ratio = 1  # keep 100% of points
num_points = filtered_points.shape[0]
sampled_indices = np.random.choice(num_points, size=int(num_points * sample_ratio), replace=False)
sampled_points = filtered_points[sampled_indices]

# compress the y values by 0.5 to make the point clouds denser in y direction
sampled_points[:,1] = sampled_points[:,1] * 0.5
# compress the z values by 0.7 to make the point clouds denser in z direction
sampled_points[:,2] = sampled_points[:,2] * 0.3

print(f"Points after down sampling: {sampled_points.shape[0]}")
# plot down sampled point clouds
fig = plt.figure(figsize=(13,13))
ax = fig.add_subplot(111, projection='3d')
# color by z value
sc = ax.scatter(sampled_points[:,0], sampled_points[:,1], sampled_points[:,2], c=sampled_points[:,2], cmap='viridis', s=1)
ax.set_xlabel('X')
ax.set_ylabel('Y')
ax.set_zlabel('Z')
# make all axes the same scale
ax.set_aspect('equal', adjustable='box')
# plt.colorbar(sc, ax=ax, label='Z value', shrink=0.3)
plt.show()
Points after down sampling: 24507
Figure
No description has been provided for this image
In [9]:
# check a slice in the middle
y_middle = (np.min(sampled_points[:,1]) + np.max(sampled_points[:,1])) / 2
slice_thickness = 0.1
middle_slice = sampled_points[(sampled_points[:,1] >= y_middle - slice_thickness/2) & (sampled_points[:,1] < y_middle + slice_thickness/2)]
plt.figure()
plt.scatter(middle_slice[:,0], middle_slice[:,2], s=1)
plt.title('Middle Slice in XZ plane after Down Sampling')
plt.xlabel('X')
plt.ylabel('Z')
plt.show()

# the slice looks good, the distance of points between the z and x direction are comparable now.
Figure
No description has been provided for this image
In [10]:
# show some slices along the x axis
x_min = np.min(sampled_points[:,0])
x_max = np.max(sampled_points[:,0])
slice_thickness = 0.5
x = x_min
while x < x_max:
    slice_points = sampled_points[(sampled_points[:,0] >= x) & (sampled_points[:,0] < x + slice_thickness)]
    plt.figure()
    plt.scatter(slice_points[:,1], slice_points[:,2], s=1)
    plt.title(f'Slice along X axis from {x:.2f} to {x + slice_thickness:.2f} in YZ plane')
    plt.xlabel('Y')
    plt.ylabel('Z')
    plt.xlim(np.min(sampled_points[:,1]), np.max(sampled_points[:,1]))
    plt.ylim(np.min(sampled_points[:,2]), np.max(sampled_points[:,2]))
    plt.show()
    x += slice_thickness
# we can see that it does well in some areas, but in some areas, leaves are still merged together or cut into different clusters.
# this is because
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
/tmp/ipykernel_1574320/2072953540.py:8: RuntimeWarning: More than 20 figures have been opened. Figures created through the pyplot interface (`matplotlib.pyplot.figure`) are retained until explicitly closed and may consume too much memory. (To control this warning, see the rcParam `figure.max_open_warning`). Consider using `matplotlib.pyplot.close()`.
  plt.figure()
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image

Use DBSCAN to find leaf clusters¶

We can see that the distance between points are not uniform across the tree. It is affected by:

  1. The distance from the LiDAR scanner to the leaf surface.
  2. The angle between the leaf surface normal and the direction from the LiDAR scanner to the leaf surface.

DBSCAN requires a fixed distance threshold (eps) to cluster points. Therefore, we will cut the tree into smaller clusters first, then apply DBSCAN on each smaller cluster with an appropriate eps value.

Clustering the tree into smaller clusters¶

In [11]:
# use DBSCAN to create clusters of points (branches and leaves)
from sklearn.cluster import DBSCAN

# initial cluster
y_scale = 1
scaled_points = sampled_points.copy()
scaled_points[:,1] = scaled_points[:,1] * y_scale
eps = 0.08
dbscan = DBSCAN(eps=eps, min_samples=5, n_jobs=14)
labels = dbscan.fit_predict(scaled_points)
num_clusters = len(set(labels)) - (1 if -1 in labels else 0)

# plot clusters with different colors
fig = plt.figure(figsize=(13,13))
ax = fig.add_subplot(111, projection='3d')  
# remove points which belong to no cluster (label = -1)
valid_indices = labels != -1
sampled_points_plot = scaled_points[valid_indices]
labels_plot = labels[valid_indices] 
sc = ax.scatter(sampled_points_plot[:,0], sampled_points_plot[:,1], sampled_points_plot[:,2], c=labels_plot, cmap='viridis', s=10)
ax.set_xlabel('X')
ax.set_ylabel('Y')
ax.set_zlabel('Z')
plt.colorbar(sc, ax=ax, label='Cluster Label', shrink=0.3)
plt.show()
Figure
No description has been provided for this image

For each smaller cluster, find leaf clusters using DBSCAN and shape analysis¶

In [60]:
# for each large cluster, find the best y_scale, z_scale to maximize the number of leaf-like clusters

from sklearn.decomposition import PCA

# analyze the shape of clusters, we want the shape that characterize leaves best
def analyze_cluster_shape(points):
    """Analyze the shape of a cluster of points using PCA."""
    if points.shape[0] < 3:
        return 0.0, 0.0, 0.0  # not enough points to analyze shape
    
    # get linearality, planarity, sphericity
    pca = PCA(n_components=3)
    pca.fit(points)
    eigenvalues = pca.explained_variance_
    total_variance = np.sum(eigenvalues)
    linearity = (eigenvalues[0] - eigenvalues[1]) / total_variance
    planarity = (eigenvalues[1] - eigenvalues[2]) / total_variance
    sphericity = eigenvalues[2] / total_variance
    return linearity, planarity, sphericity

# leaf-like clusters are defined as clusters with size between certain sizes, and planarity > linearity and sphericity
def cluster_is_leaf_like(cluster_points):
    linearity, planarity, sphericity = analyze_cluster_shape(cluster_points)
    ratio = planarity / (sphericity + 1e-7)
    if cluster_points.shape[0] >= 15 and cluster_points.shape[0] <= 150 and ratio >= 20:
        return True, linearity, planarity, sphericity
    return False, linearity, planarity, sphericity


def score_function(points, labels):
    cluster_id_2_stats = {}
    for cluster_label in set(labels):
        if cluster_label == -1:
            continue  # skip noise
        cluster_points = points[labels == cluster_label]
        is_leaf, linearity, planarity, sphericity = cluster_is_leaf_like(cluster_points)
        if is_leaf:
            cluster_id_2_stats[cluster_label] = (linearity, planarity, sphericity)
            
    # score is planarity * number of points in each leaf-like cluster
    score = 0
    for cluster_label, stats in cluster_id_2_stats.items():
        planarity = stats[1]
        num_points = np.sum(labels == cluster_label)
        score += num_points
    return score, cluster_id_2_stats

def optimize_scales_for_cluster(cluster_points):
    best_y_scale = 1.0
    best_z_scale = 1.0
    best_score = -1
    best_num_leaf_clusters = 0
    best_min_samples = 5
    
    list_y_scale = np.arange(0.5, 2.0, 0.2)
    list_z_scale = np.arange(0.5, 2.0, 0.2)
    list_min_samples = [5, 7, 9]
    
    for min_samples in list_min_samples:
        for y_scale in list_y_scale:
            for z_scale in list_z_scale:
                scaled_points = cluster_points.copy()
                scaled_points[:,1] = scaled_points[:,1] * y_scale
                scaled_points[:,2] = scaled_points[:,2] * z_scale
                
                dbscan = DBSCAN(eps=0.05, min_samples=min_samples, n_jobs=16)
                labels = dbscan.fit_predict(scaled_points)
                
                # the number of points in -1 cluster should be less than 20% of total points
                num_noise_points = np.sum(labels == -1)
                if num_noise_points > 0.2 * scaled_points.shape[0]:
                    continue  # skip this scale
                
                score, cluster_id_2_stats = score_function(scaled_points, labels)
                
                if score > best_score or (np.abs(score - best_score) <= 3 and len(cluster_id_2_stats) > best_num_leaf_clusters):
                    best_score = score
                    best_y_scale = y_scale
                    best_z_scale = z_scale
                    best_num_leaf_clusters = len(cluster_id_2_stats)
                    best_min_samples = min_samples
                
    return best_y_scale, best_z_scale, best_score, best_num_leaf_clusters, best_min_samples
In [61]:
cluster_id_2_best_scales = {}
In [62]:
for cluster_label in set(labels):
    if cluster_label in cluster_id_2_best_scales:
        continue  # already processed
    
    if cluster_label == -1:
        continue  # skip noise
    cluster_points = scaled_points[labels == cluster_label]
    # if cluster_points.shape[0] < 100:
    #     continue  # skip small clusters
    
    best_y_scale, best_z_scale, best_score, best_num_leaf_clusters, best_min_samples = optimize_scales_for_cluster(cluster_points)
    print(f"Cluster {cluster_label}: Best Y scale: {best_y_scale:.2f}, Best Z scale: {best_z_scale:.2f}, Best Score (leaf-like clusters): {best_score}, Number of leaf-like clusters: {best_num_leaf_clusters}")
    cluster_id_2_best_scales[cluster_label] = (best_y_scale, best_z_scale, best_score, best_num_leaf_clusters, best_min_samples)
Cluster 0: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 35, Number of leaf-like clusters: 1
Cluster 1: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 110, Number of leaf-like clusters: 4
Cluster 2: Best Y scale: 0.90, Best Z scale: 0.50, Best Score (leaf-like clusters): 43, Number of leaf-like clusters: 1
Cluster 3: Best Y scale: 1.70, Best Z scale: 1.70, Best Score (leaf-like clusters): 646, Number of leaf-like clusters: 14
Cluster 4: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 16, Number of leaf-like clusters: 1
Cluster 5: Best Y scale: 0.90, Best Z scale: 0.50, Best Score (leaf-like clusters): 60, Number of leaf-like clusters: 2
Cluster 6: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 37, Number of leaf-like clusters: 1
Cluster 7: Best Y scale: 1.10, Best Z scale: 0.50, Best Score (leaf-like clusters): 67, Number of leaf-like clusters: 3
Cluster 8: Best Y scale: 0.90, Best Z scale: 1.90, Best Score (leaf-like clusters): 104, Number of leaf-like clusters: 4
Cluster 9: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 61, Number of leaf-like clusters: 2
Cluster 10: Best Y scale: 1.10, Best Z scale: 1.90, Best Score (leaf-like clusters): 435, Number of leaf-like clusters: 11
Cluster 11: Best Y scale: 0.90, Best Z scale: 1.70, Best Score (leaf-like clusters): 47, Number of leaf-like clusters: 2
Cluster 12: Best Y scale: 0.50, Best Z scale: 1.90, Best Score (leaf-like clusters): 160, Number of leaf-like clusters: 2
Cluster 13: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 61, Number of leaf-like clusters: 1
Cluster 14: Best Y scale: 1.10, Best Z scale: 1.10, Best Score (leaf-like clusters): 69, Number of leaf-like clusters: 2
Cluster 15: Best Y scale: 0.50, Best Z scale: 1.30, Best Score (leaf-like clusters): 21, Number of leaf-like clusters: 1
Cluster 16: Best Y scale: 0.90, Best Z scale: 0.50, Best Score (leaf-like clusters): 115, Number of leaf-like clusters: 2
Cluster 17: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 18: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 42, Number of leaf-like clusters: 1
Cluster 19: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 43, Number of leaf-like clusters: 1
Cluster 20: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 57, Number of leaf-like clusters: 2
Cluster 21: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 22: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 29, Number of leaf-like clusters: 1
Cluster 23: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 54, Number of leaf-like clusters: 1
Cluster 24: Best Y scale: 0.50, Best Z scale: 1.90, Best Score (leaf-like clusters): 71, Number of leaf-like clusters: 2
Cluster 25: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 69, Number of leaf-like clusters: 1
Cluster 26: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 72, Number of leaf-like clusters: 1
Cluster 27: Best Y scale: 0.70, Best Z scale: 1.30, Best Score (leaf-like clusters): 222, Number of leaf-like clusters: 6
Cluster 28: Best Y scale: 0.50, Best Z scale: 1.90, Best Score (leaf-like clusters): 68, Number of leaf-like clusters: 2
Cluster 29: Best Y scale: 0.90, Best Z scale: 0.70, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 30: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 29, Number of leaf-like clusters: 1
Cluster 31: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 33, Number of leaf-like clusters: 1
Cluster 32: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 52, Number of leaf-like clusters: 1
Cluster 33: Best Y scale: 0.70, Best Z scale: 1.30, Best Score (leaf-like clusters): 25, Number of leaf-like clusters: 1
Cluster 34: Best Y scale: 0.90, Best Z scale: 1.10, Best Score (leaf-like clusters): 165, Number of leaf-like clusters: 2
Cluster 35: Best Y scale: 0.90, Best Z scale: 1.30, Best Score (leaf-like clusters): 80, Number of leaf-like clusters: 3
Cluster 36: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 31, Number of leaf-like clusters: 1
Cluster 37: Best Y scale: 0.70, Best Z scale: 1.90, Best Score (leaf-like clusters): 158, Number of leaf-like clusters: 2
Cluster 38: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 27, Number of leaf-like clusters: 1
Cluster 39: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 171, Number of leaf-like clusters: 4
Cluster 40: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 146, Number of leaf-like clusters: 2
Cluster 41: Best Y scale: 0.50, Best Z scale: 1.90, Best Score (leaf-like clusters): 110, Number of leaf-like clusters: 2
Cluster 42: Best Y scale: 1.10, Best Z scale: 0.70, Best Score (leaf-like clusters): 92, Number of leaf-like clusters: 2
Cluster 43: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 33, Number of leaf-like clusters: 1
Cluster 44: Best Y scale: 1.90, Best Z scale: 1.30, Best Score (leaf-like clusters): 396, Number of leaf-like clusters: 7
Cluster 45: Best Y scale: 1.10, Best Z scale: 0.90, Best Score (leaf-like clusters): 174, Number of leaf-like clusters: 2
Cluster 46: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 47: Best Y scale: 0.90, Best Z scale: 1.90, Best Score (leaf-like clusters): 234, Number of leaf-like clusters: 4
Cluster 48: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 31, Number of leaf-like clusters: 1
Cluster 49: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 23, Number of leaf-like clusters: 1
Cluster 50: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 217, Number of leaf-like clusters: 7
Cluster 51: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 34, Number of leaf-like clusters: 1
Cluster 52: Best Y scale: 1.90, Best Z scale: 0.50, Best Score (leaf-like clusters): 51, Number of leaf-like clusters: 1
Cluster 53: Best Y scale: 0.70, Best Z scale: 0.90, Best Score (leaf-like clusters): 72, Number of leaf-like clusters: 1
Cluster 54: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 36, Number of leaf-like clusters: 1
Cluster 55: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 29, Number of leaf-like clusters: 1
Cluster 56: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 57: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 173, Number of leaf-like clusters: 5
Cluster 58: Best Y scale: 0.70, Best Z scale: 1.70, Best Score (leaf-like clusters): 278, Number of leaf-like clusters: 11
Cluster 59: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 60: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 52, Number of leaf-like clusters: 1
Cluster 61: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 62: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 25, Number of leaf-like clusters: 1
Cluster 63: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 64: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 56, Number of leaf-like clusters: 1
Cluster 65: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 72, Number of leaf-like clusters: 2
Cluster 66: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 35, Number of leaf-like clusters: 1
Cluster 67: Best Y scale: 0.70, Best Z scale: 1.10, Best Score (leaf-like clusters): 16, Number of leaf-like clusters: 1
Cluster 68: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 69: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 28, Number of leaf-like clusters: 1
Cluster 70: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 75, Number of leaf-like clusters: 1
Cluster 71: Best Y scale: 1.30, Best Z scale: 0.50, Best Score (leaf-like clusters): 37, Number of leaf-like clusters: 1
Cluster 72: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 73: Best Y scale: 0.50, Best Z scale: 1.30, Best Score (leaf-like clusters): 72, Number of leaf-like clusters: 2
Cluster 74: Best Y scale: 1.30, Best Z scale: 0.90, Best Score (leaf-like clusters): 109, Number of leaf-like clusters: 3
Cluster 75: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 66, Number of leaf-like clusters: 1
Cluster 76: Best Y scale: 0.70, Best Z scale: 1.30, Best Score (leaf-like clusters): 69, Number of leaf-like clusters: 1
Cluster 77: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 25, Number of leaf-like clusters: 1
Cluster 78: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 65, Number of leaf-like clusters: 1
Cluster 79: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 80, Number of leaf-like clusters: 2
Cluster 80: Best Y scale: 1.10, Best Z scale: 1.90, Best Score (leaf-like clusters): 127, Number of leaf-like clusters: 3
Cluster 81: Best Y scale: 0.70, Best Z scale: 1.30, Best Score (leaf-like clusters): 75, Number of leaf-like clusters: 2
Cluster 82: Best Y scale: 0.70, Best Z scale: 1.10, Best Score (leaf-like clusters): 51, Number of leaf-like clusters: 2
Cluster 83: Best Y scale: 0.90, Best Z scale: 0.90, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 84: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 85: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 37, Number of leaf-like clusters: 1
Cluster 86: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 58, Number of leaf-like clusters: 1
Cluster 87: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 45, Number of leaf-like clusters: 1
Cluster 88: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 89: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 38, Number of leaf-like clusters: 1
Cluster 90: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 91: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 65, Number of leaf-like clusters: 1
Cluster 92: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 20, Number of leaf-like clusters: 1
Cluster 93: Best Y scale: 0.90, Best Z scale: 0.90, Best Score (leaf-like clusters): 91, Number of leaf-like clusters: 3
Cluster 94: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 46, Number of leaf-like clusters: 1
Cluster 95: Best Y scale: 0.90, Best Z scale: 0.50, Best Score (leaf-like clusters): 89, Number of leaf-like clusters: 1
Cluster 96: Best Y scale: 1.10, Best Z scale: 0.50, Best Score (leaf-like clusters): 35, Number of leaf-like clusters: 1
Cluster 97: Best Y scale: 0.50, Best Z scale: 1.30, Best Score (leaf-like clusters): 163, Number of leaf-like clusters: 2
Cluster 98: Best Y scale: 1.10, Best Z scale: 1.90, Best Score (leaf-like clusters): 43, Number of leaf-like clusters: 2
Cluster 99: Best Y scale: 0.90, Best Z scale: 1.90, Best Score (leaf-like clusters): 40, Number of leaf-like clusters: 1
Cluster 100: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 101: Best Y scale: 0.90, Best Z scale: 1.90, Best Score (leaf-like clusters): 40, Number of leaf-like clusters: 1
Cluster 102: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 103: Best Y scale: 0.70, Best Z scale: 0.50, Best Score (leaf-like clusters): 31, Number of leaf-like clusters: 1
Cluster 104: Best Y scale: 0.70, Best Z scale: 1.90, Best Score (leaf-like clusters): 134, Number of leaf-like clusters: 5
Cluster 105: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 51, Number of leaf-like clusters: 1
Cluster 106: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 23, Number of leaf-like clusters: 1
Cluster 107: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 154, Number of leaf-like clusters: 2
Cluster 108: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 109: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 110: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 71, Number of leaf-like clusters: 2
Cluster 111: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 54, Number of leaf-like clusters: 1
Cluster 112: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 28, Number of leaf-like clusters: 1
Cluster 113: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 51, Number of leaf-like clusters: 1
Cluster 114: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 204, Number of leaf-like clusters: 3
Cluster 115: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 116: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 51, Number of leaf-like clusters: 1
Cluster 117: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 44, Number of leaf-like clusters: 1
Cluster 118: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 28, Number of leaf-like clusters: 1
Cluster 119: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 36, Number of leaf-like clusters: 1
Cluster 120: Best Y scale: 0.70, Best Z scale: 1.30, Best Score (leaf-like clusters): 34, Number of leaf-like clusters: 1
Cluster 121: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 122: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 55, Number of leaf-like clusters: 1
Cluster 123: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 42, Number of leaf-like clusters: 1
Cluster 124: Best Y scale: 1.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 40, Number of leaf-like clusters: 2
Cluster 125: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 39, Number of leaf-like clusters: 1
Cluster 126: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 127: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 128: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 54, Number of leaf-like clusters: 2
Cluster 129: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 130: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 131: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 49, Number of leaf-like clusters: 1
Cluster 132: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 21, Number of leaf-like clusters: 1
Cluster 133: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 16, Number of leaf-like clusters: 1
Cluster 134: Best Y scale: 0.90, Best Z scale: 1.90, Best Score (leaf-like clusters): 95, Number of leaf-like clusters: 3
Cluster 135: Best Y scale: 0.70, Best Z scale: 1.50, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 136: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 137: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 28, Number of leaf-like clusters: 1
Cluster 138: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 139: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 67, Number of leaf-like clusters: 2
Cluster 140: Best Y scale: 0.90, Best Z scale: 1.90, Best Score (leaf-like clusters): 90, Number of leaf-like clusters: 2
Cluster 141: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 36, Number of leaf-like clusters: 1
Cluster 142: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 101, Number of leaf-like clusters: 1
Cluster 143: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 27, Number of leaf-like clusters: 1
Cluster 144: Best Y scale: 0.70, Best Z scale: 1.90, Best Score (leaf-like clusters): 18, Number of leaf-like clusters: 1
Cluster 145: Best Y scale: 0.70, Best Z scale: 1.90, Best Score (leaf-like clusters): 58, Number of leaf-like clusters: 2
Cluster 146: Best Y scale: 1.30, Best Z scale: 1.90, Best Score (leaf-like clusters): 35, Number of leaf-like clusters: 2
Cluster 147: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 32, Number of leaf-like clusters: 1
Cluster 148: Best Y scale: 0.50, Best Z scale: 1.30, Best Score (leaf-like clusters): 25, Number of leaf-like clusters: 1
Cluster 149: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 150: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 151: Best Y scale: 0.50, Best Z scale: 1.30, Best Score (leaf-like clusters): 77, Number of leaf-like clusters: 2
Cluster 152: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 153: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 37, Number of leaf-like clusters: 1
Cluster 154: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 50, Number of leaf-like clusters: 1
Cluster 155: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 33, Number of leaf-like clusters: 1
Cluster 156: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 55, Number of leaf-like clusters: 3
Cluster 157: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 22, Number of leaf-like clusters: 1
Cluster 158: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 159: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 49, Number of leaf-like clusters: 1
Cluster 160: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 71, Number of leaf-like clusters: 1
Cluster 161: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 21, Number of leaf-like clusters: 1
Cluster 162: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 63, Number of leaf-like clusters: 1
Cluster 163: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 37, Number of leaf-like clusters: 1
Cluster 164: Best Y scale: 0.70, Best Z scale: 0.90, Best Score (leaf-like clusters): 71, Number of leaf-like clusters: 3
Cluster 165: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 33, Number of leaf-like clusters: 1
Cluster 166: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 39, Number of leaf-like clusters: 1
Cluster 167: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 47, Number of leaf-like clusters: 1
Cluster 168: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 169: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 21, Number of leaf-like clusters: 1
Cluster 170: Best Y scale: 0.70, Best Z scale: 1.70, Best Score (leaf-like clusters): 35, Number of leaf-like clusters: 1
Cluster 171: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 172: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 31, Number of leaf-like clusters: 1
Cluster 173: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 174: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 175: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 176: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 15, Number of leaf-like clusters: 1
Cluster 177: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 178: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 32, Number of leaf-like clusters: 1
Cluster 179: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 180: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 42, Number of leaf-like clusters: 1
Cluster 181: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 182: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 25, Number of leaf-like clusters: 1
Cluster 183: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 50, Number of leaf-like clusters: 1
Cluster 184: Best Y scale: 1.10, Best Z scale: 0.50, Best Score (leaf-like clusters): 15, Number of leaf-like clusters: 1
Cluster 185: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 32, Number of leaf-like clusters: 1
Cluster 186: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 187: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 188: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 189: Best Y scale: 0.50, Best Z scale: 1.90, Best Score (leaf-like clusters): 27, Number of leaf-like clusters: 1
Cluster 190: Best Y scale: 0.50, Best Z scale: 1.30, Best Score (leaf-like clusters): 37, Number of leaf-like clusters: 1
Cluster 191: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 21, Number of leaf-like clusters: 1
Cluster 192: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 46, Number of leaf-like clusters: 1
Cluster 193: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 43, Number of leaf-like clusters: 1
Cluster 194: Best Y scale: 0.70, Best Z scale: 1.90, Best Score (leaf-like clusters): 25, Number of leaf-like clusters: 1
Cluster 195: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 64, Number of leaf-like clusters: 1
Cluster 196: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 58, Number of leaf-like clusters: 1
Cluster 197: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 38, Number of leaf-like clusters: 1
Cluster 198: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 199: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 52, Number of leaf-like clusters: 1
Cluster 200: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 201: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 21, Number of leaf-like clusters: 1
Cluster 202: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 20, Number of leaf-like clusters: 1
Cluster 203: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 204: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 29, Number of leaf-like clusters: 1
Cluster 205: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 61, Number of leaf-like clusters: 1
Cluster 206: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 207: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 208: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 49, Number of leaf-like clusters: 2
Cluster 209: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 210: Best Y scale: 1.10, Best Z scale: 1.90, Best Score (leaf-like clusters): 84, Number of leaf-like clusters: 3
Cluster 211: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 212: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 35, Number of leaf-like clusters: 1
Cluster 213: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 214: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 215: Best Y scale: 1.90, Best Z scale: 0.50, Best Score (leaf-like clusters): 30, Number of leaf-like clusters: 1
Cluster 216: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 217: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 33, Number of leaf-like clusters: 1
Cluster 218: Best Y scale: 0.70, Best Z scale: 0.50, Best Score (leaf-like clusters): 34, Number of leaf-like clusters: 1
Cluster 219: Best Y scale: 1.30, Best Z scale: 1.30, Best Score (leaf-like clusters): 42, Number of leaf-like clusters: 2
Cluster 220: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 33, Number of leaf-like clusters: 1
Cluster 221: Best Y scale: 0.50, Best Z scale: 1.90, Best Score (leaf-like clusters): 45, Number of leaf-like clusters: 1
Cluster 222: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 223: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 25, Number of leaf-like clusters: 1
Cluster 224: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 60, Number of leaf-like clusters: 2
Cluster 225: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 18, Number of leaf-like clusters: 1
Cluster 226: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 227: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 228: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 37, Number of leaf-like clusters: 1
Cluster 229: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 230: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 38, Number of leaf-like clusters: 1
Cluster 231: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 22, Number of leaf-like clusters: 1
Cluster 232: Best Y scale: 1.30, Best Z scale: 0.50, Best Score (leaf-like clusters): 38, Number of leaf-like clusters: 1
Cluster 233: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 234: Best Y scale: 0.50, Best Z scale: 1.90, Best Score (leaf-like clusters): 70, Number of leaf-like clusters: 3
Cluster 235: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 31, Number of leaf-like clusters: 1
Cluster 236: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 20, Number of leaf-like clusters: 1
Cluster 237: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 238: Best Y scale: 0.50, Best Z scale: 1.30, Best Score (leaf-like clusters): 16, Number of leaf-like clusters: 1
Cluster 239: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 45, Number of leaf-like clusters: 1
Cluster 240: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 241: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 22, Number of leaf-like clusters: 1
Cluster 242: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 243: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 18, Number of leaf-like clusters: 1
Cluster 244: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 71, Number of leaf-like clusters: 1
Cluster 245: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 32, Number of leaf-like clusters: 1
Cluster 246: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 28, Number of leaf-like clusters: 1
Cluster 247: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 39, Number of leaf-like clusters: 1
Cluster 248: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 249: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 27, Number of leaf-like clusters: 1
Cluster 250: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 251: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 27, Number of leaf-like clusters: 1
Cluster 252: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 253: Best Y scale: 0.70, Best Z scale: 0.50, Best Score (leaf-like clusters): 37, Number of leaf-like clusters: 1
Cluster 254: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 255: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 36, Number of leaf-like clusters: 1
Cluster 256: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 58, Number of leaf-like clusters: 1
Cluster 257: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 258: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 22, Number of leaf-like clusters: 1
Cluster 259: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 20, Number of leaf-like clusters: 1
Cluster 260: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 37, Number of leaf-like clusters: 1
Cluster 261: Best Y scale: 0.90, Best Z scale: 0.50, Best Score (leaf-like clusters): 16, Number of leaf-like clusters: 1
Cluster 262: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 15, Number of leaf-like clusters: 1
Cluster 263: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 264: Best Y scale: 0.50, Best Z scale: 1.30, Best Score (leaf-like clusters): 20, Number of leaf-like clusters: 1
Cluster 265: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 266: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 267: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 36, Number of leaf-like clusters: 1
Cluster 268: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 269: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 23, Number of leaf-like clusters: 1
Cluster 270: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 271: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 29, Number of leaf-like clusters: 1
Cluster 272: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 23, Number of leaf-like clusters: 1
Cluster 273: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 36, Number of leaf-like clusters: 1
Cluster 274: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 275: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 28, Number of leaf-like clusters: 1
Cluster 276: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 277: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 278: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 44, Number of leaf-like clusters: 1
Cluster 279: Best Y scale: 1.10, Best Z scale: 0.50, Best Score (leaf-like clusters): 19, Number of leaf-like clusters: 1
Cluster 280: Best Y scale: 0.70, Best Z scale: 0.70, Best Score (leaf-like clusters): 18, Number of leaf-like clusters: 1
Cluster 281: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 282: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 34, Number of leaf-like clusters: 1
Cluster 283: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 284: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 20, Number of leaf-like clusters: 1
Cluster 285: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 286: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 28, Number of leaf-like clusters: 1
Cluster 287: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 288: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 289: Best Y scale: 0.90, Best Z scale: 0.50, Best Score (leaf-like clusters): 34, Number of leaf-like clusters: 1
Cluster 290: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 291: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 54, Number of leaf-like clusters: 1
Cluster 292: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 293: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 22, Number of leaf-like clusters: 1
Cluster 294: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 295: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 296: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 297: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 21, Number of leaf-like clusters: 1
Cluster 298: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 299: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 15, Number of leaf-like clusters: 1
Cluster 300: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 301: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 302: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 303: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 304: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 305: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 46, Number of leaf-like clusters: 1
Cluster 306: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 307: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 308: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 309: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 310: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 25, Number of leaf-like clusters: 1
Cluster 311: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 312: Best Y scale: 0.50, Best Z scale: 0.90, Best Score (leaf-like clusters): 16, Number of leaf-like clusters: 1
Cluster 313: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 35, Number of leaf-like clusters: 1
Cluster 314: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 315: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 316: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 317: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 318: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 22, Number of leaf-like clusters: 1
Cluster 319: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 53, Number of leaf-like clusters: 1
Cluster 320: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 321: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 322: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 323: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 324: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 325: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 326: Best Y scale: 0.70, Best Z scale: 1.30, Best Score (leaf-like clusters): 34, Number of leaf-like clusters: 1
Cluster 327: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 18, Number of leaf-like clusters: 1
Cluster 328: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 329: Best Y scale: 1.10, Best Z scale: 0.50, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 330: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 331: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 332: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 333: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 334: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 335: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 20, Number of leaf-like clusters: 1
Cluster 336: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 337: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 338: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 339: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 340: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 341: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 342: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 343: Best Y scale: 1.30, Best Z scale: 0.70, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Cluster 344: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 345: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 346: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 347: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 348: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 349: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 350: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 351: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 24, Number of leaf-like clusters: 1
Cluster 352: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 353: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 354: Best Y scale: 1.10, Best Z scale: 1.90, Best Score (leaf-like clusters): 15, Number of leaf-like clusters: 1
Cluster 355: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 356: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 357: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 358: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 359: Best Y scale: 0.50, Best Z scale: 1.50, Best Score (leaf-like clusters): 26, Number of leaf-like clusters: 1
Cluster 360: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 361: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 362: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 363: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 364: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 365: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 366: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 367: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 368: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 369: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 370: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 371: Best Y scale: 0.50, Best Z scale: 1.70, Best Score (leaf-like clusters): 20, Number of leaf-like clusters: 1
Cluster 372: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 373: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 374: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 375: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 376: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 377: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 378: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 379: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 380: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 381: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 382: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 383: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 384: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 385: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 386: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 387: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 388: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 389: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 390: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 391: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 392: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 393: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 394: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 395: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 396: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 397: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 398: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 399: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 400: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 401: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 402: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 403: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 404: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 405: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 406: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 407: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 408: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 409: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
Cluster 410: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Cluster 411: Best Y scale: 1.00, Best Z scale: 1.00, Best Score (leaf-like clusters): -1, Number of leaf-like clusters: 0
In [65]:
# plot best y and best z scales of all clusters with more than 0 leaf-like clusters
best_y_scales = []
best_z_scales = []
for cluster_label, scales in cluster_id_2_best_scales.items():
    best_y_scale, best_z_scale, best_score, best_num_leaf_clusters, best_min_samples = scales
    if best_num_leaf_clusters > 0:
        best_y_scales.append(best_y_scale)
        best_z_scales.append(best_z_scale)
# plot 3d histogram
fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')
hist, xedges, yedges = np.histogram2d(best_y_scales, best_z_scales, bins=10, range=[[0.5, 2.0], [0.5, 2.0]])
xpos, ypos = np.meshgrid(xedges[:-1], yedges[:-1], indexing="ij")
xpos = xpos.ravel()
ypos = ypos.ravel()
zpos = 0
dx = dy = 0.1 * np.ones_like(zpos)
dz = hist.ravel()   
ax.bar3d(xpos, ypos, zpos, dx, dy, dz, zsort='average')
ax.set_xlabel('Best Y Scale')
ax.set_ylabel('Best Z Scale')
ax.set_zlabel('Number of Clusters')
plt.show()
Figure
No description has been provided for this image
In [66]:
# plot some random clusters with their best scales
for cluster_label in np.random.choice(list(cluster_id_2_best_scales.keys()), size=5, replace=False):
    best_y_scale, best_z_scale, best_score, best_num_leaf_clusters, best_min_samples = cluster_id_2_best_scales[cluster_label]
    print(f"Cluster {cluster_label}: Best Y scale: {best_y_scale:.2f}, Best Z scale: {best_z_scale:.2f}, Best Score (leaf-like clusters): {best_score}, Number of leaf-like clusters: {best_num_leaf_clusters}")
    cluster_points = scaled_points[labels == cluster_label]
    
    # plot clusters with different colors
    large_cluster = cluster_points.copy()
    large_cluster[:,1] = large_cluster[:,1] * best_y_scale
    large_cluster[:,2] = large_cluster[:,2] * best_z_scale 
    sub_dbscan = DBSCAN(eps=0.05, min_samples=best_min_samples, n_jobs=16)
    sub_labels = sub_dbscan.fit_predict(large_cluster)
    
    fig = plt.figure(figsize=(10,10))
    ax = fig.add_subplot(111, projection='3d')
    valid_indices = sub_labels != -1
    sampled_points_plot = large_cluster[valid_indices]
    labels_plot = sub_labels[valid_indices]
    sc = ax.scatter(sampled_points_plot[:,0], sampled_points_plot[:,1], sampled_points_plot[:,2], c=labels_plot, cmap='viridis', s=10)
    ax.set_xlabel('X')
    ax.set_ylabel('Y')
    ax.set_zlabel('Z')
    # plot true scale 
    ax.set_aspect('equal', adjustable='box')
    plt.tight_layout()
    plt.show()
Cluster 245: Best Y scale: 0.50, Best Z scale: 0.70, Best Score (leaf-like clusters): 32, Number of leaf-like clusters: 1
Figure
No description has been provided for this image
Cluster 78: Best Y scale: 0.50, Best Z scale: 1.10, Best Score (leaf-like clusters): 65, Number of leaf-like clusters: 1
Figure
No description has been provided for this image
Cluster 63: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 0, Number of leaf-like clusters: 0
Figure
No description has been provided for this image
Cluster 36: Best Y scale: 0.50, Best Z scale: 0.50, Best Score (leaf-like clusters): 31, Number of leaf-like clusters: 1
Figure
No description has been provided for this image
Cluster 83: Best Y scale: 0.90, Best Z scale: 0.90, Best Score (leaf-like clusters): 17, Number of leaf-like clusters: 1
Figure
No description has been provided for this image
In [41]:
# assert False
In [42]:
# dump cluster_id_2_best_scales to a file
# import pickle
# with open('cluster_id_2_best_scales_v5.pkl', 'wb') as f:
#     pickle.dump(cluster_id_2_best_scales, f)
    
# # dump all points and their cluster labels to a file
# import pandas as pd
# df = pd.DataFrame(scaled_points, columns=['X', 'Y', 'Z'])
# df['ClusterLabel'] = labels
# df.to_csv('scaled_points_with_clusters_v5.csv', index=False)

# # load cluster_id_2_best_scales from a file
# import pickle
# with open('cluster_id_2_best_scales_v5.pkl', 'rb') as f:
#     cluster_id_2_best_scales = pickle.load(f)
    
# # load all points and their cluster labels from a file
# import pandas as pd
# df = pd.read_csv('scaled_points_with_clusters_v5.csv')
# scaled_points = df[['X', 'Y', 'Z']].values
# labels = df['ClusterLabel'].values  

Visualize the final result¶

In [67]:
# add sub-cluster labels to the main labels but origianl labels * 10 + sub-cluster labels
new_labels = labels.copy()
is_leaf_label = np.zeros_like(labels, dtype=bool)
for cluster_label in set(labels):
    if cluster_label == -1:
        continue  # skip noise
    cluster_points = scaled_points[labels == cluster_label]
    
    if cluster_label not in cluster_id_2_best_scales:
        continue  # skip clusters that were not processed
    best_y_scale, best_z_scale, best_score, best_num_leaf_clusters, best_min_samples = cluster_id_2_best_scales[cluster_label]
    
    large_cluster = cluster_points.copy()
    large_cluster[:,1] = large_cluster[:,1] * best_y_scale
    large_cluster[:,2] = large_cluster[:,2] * best_z_scale 
    sub_dbscan = DBSCAN(eps=0.05, min_samples=best_min_samples, n_jobs=14)
    sub_labels = sub_dbscan.fit_predict(large_cluster)
    
    for i, point in enumerate(cluster_points):
        global_index = np.where((scaled_points == point).all(axis=1))[0][0]
        if sub_labels[i] == -1:
            continue  # skip noise
        new_labels[global_index] = cluster_label * 10 + sub_labels[i]
        
        # check if this sub-cluster is leaf-like
        cluster_points_sub = large_cluster[sub_labels == sub_labels[i]]
        is_leaf, _, _, _ = cluster_is_leaf_like(cluster_points_sub)
        if is_leaf:
            is_leaf_label[global_index] = 1
In [68]:
unique_labels = np.unique(new_labels)
num_unique_labels = len(unique_labels) - (1 if -1 in unique_labels else 0)
# generate a random map between unique labels and colors
label_to_color = {}
for label in unique_labels:
    if label == -1:
        label_to_color[label] = (0, 0, 0)  # black for noise
    else:
        label_to_color[label] = np.random.rand(3,)
In [73]:
# plot tree using new labels
fig = plt.figure(figsize=(12,15))
ax = fig.add_subplot(111, projection='3d')  
# remove points which belong to no cluster (label = -1)
valid_indices = new_labels != -1
sampled_points_plot = scaled_points[valid_indices]
labels_plot = new_labels[valid_indices] 
colors_plot = np.array([label_to_color[label] for label in labels_plot])
# plot leaf points as triangles
leaf_indices = is_leaf_label[valid_indices]
non_leaf_indices = ~leaf_indices
ax.scatter(sampled_points_plot[non_leaf_indices,0], sampled_points_plot[non_leaf_indices,1], sampled_points_plot[non_leaf_indices,2], c=colors_plot[non_leaf_indices], s=2, alpha=0.5)
ax.scatter(sampled_points_plot[leaf_indices,0], sampled_points_plot[leaf_indices,1], sampled_points_plot[leaf_indices,2], c=colors_plot[leaf_indices], s=10, marker='^', alpha=0.7)
ax.set_xlabel('X')
ax.set_ylabel('Y')
ax.set_zlabel('Z')
plt.tight_layout()
plt.show()
Figure
No description has been provided for this image

Our estimation of number of leaves¶

In [70]:
# number of leaf clusters found is total number of num_leaf_cluster in cluster_id_2_best_scales
num_leaf = 0
for k, v in cluster_id_2_best_scales.items():
    num_leaf += v[3]
print(f"Estimated total number of leaves: {num_leaf*2}") # because we estimate on half of the point clouds
Estimated total number of leaves: 758

CT scan along z-axis¶

Triangle points is for leaf clusters and circle points is for branch clusters.

In [71]:
#  plot the tree cutting along the z axis at different heights
z_min = np.min(scaled_points[:,2])
z_max = np.max(scaled_points[:,2])
slice_thickness = 0.20
z = z_min
while z < z_max:
    slice_points = scaled_points[(scaled_points[:,2] >= z) & (scaled_points[:,2] < z + slice_thickness)]
    slice_labels = new_labels[(scaled_points[:,2] >= z) & (scaled_points[:,2] < z + slice_thickness)]
    slice_is_leaf = is_leaf_label[(scaled_points[:,2] >= z) & (scaled_points[:,2] < z + slice_thickness)]
    
    # plot the slice with cluster colors
    fig = plt.figure(figsize=(12,15))
    ax = fig.add_subplot(111)
    # valid_indices = slice_labels != -1
    # slice_points_plot = slice_points[valid_indices]
    # slice_labels_plot = slice_labels[valid_indices]
    
    slice_points_plot = slice_points
    slice_labels_plot = slice_labels
    
    colors_plot = np.array([label_to_color[label] for label in slice_labels_plot])
    # plot leaf points as triangles    
    leaf_indices = slice_is_leaf
    non_leaf_indices = ~leaf_indices
    ax.scatter(slice_points_plot[non_leaf_indices,0], slice_points_plot[non_leaf_indices,1], c=colors_plot[non_leaf_indices], s=5, alpha=0.5)
    ax.scatter(slice_points_plot[leaf_indices,0], slice_points_plot[leaf_indices,1], c=colors_plot[leaf_indices], s=10, marker='^', alpha=0.7)
    ax.set_xlabel('X')
    ax.set_ylabel('Y')
    # ax.set_aspect('equal', adjustable='box')
    ax.set_xlim(np.min(scaled_points[:,0]), np.max(scaled_points[:,0]))
    ax.set_ylim(np.min(scaled_points[:,1]), np.max(scaled_points[:,1]))
    ax.set_title(f'Slice along Z axis from {z:.2f} to {z + slice_thickness:.2f}')
    plt.tight_layout()
    plt.show()
    
    z += slice_thickness
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image

CT scan along y-axis¶

In [74]:
# slices along y axis
y_min = np.min(scaled_points[:,1])
y_max = np.max(scaled_points[:,1])
slice_thickness = 0.2
y = y_min
while y < y_max:
    slice_points = scaled_points[(scaled_points[:,1] >= y) & (scaled_points[:,1] < y + slice_thickness)]
    slice_labels = new_labels[(scaled_points[:,1] >= y) & (scaled_points[:,1] < y + slice_thickness)]
    slice_is_leaf = is_leaf_label[(scaled_points[:,1] >= y) & (scaled_points[:,1] < y + slice_thickness)]
    
    # plot the slice with cluster colors
    fig = plt.figure(figsize=(12,15))
    ax = fig.add_subplot(111)
    valid_indices = slice_labels != -1
    slice_points_plot = slice_points[valid_indices]
    slice_labels_plot = slice_labels[valid_indices]
    colors_plot = np.array([label_to_color[label] for label in slice_labels_plot])
    # plot leaf points as triangles    
    leaf_indices = slice_is_leaf[valid_indices]
    non_leaf_indices = ~leaf_indices
    ax.scatter(slice_points_plot[non_leaf_indices,0], slice_points_plot[non_leaf_indices,2], c=colors_plot[non_leaf_indices], s=5, alpha=0.5)
    ax.scatter(slice_points_plot[leaf_indices,0], slice_points_plot[leaf_indices,2], c=colors_plot[leaf_indices], s=10, marker='^', alpha=0.7)
    ax.set_xlabel('X')
    ax.set_ylabel('Z')
    # ax.set_aspect('equal', adjustable='box')
    ax.set_xlim(np.min(scaled_points[:,0]), np.max(scaled_points[:,0]))
    ax.set_ylim(np.min(scaled_points[:,2]), np.max(scaled_points[:,2]))
    ax.set_title(f'Slice along Y axis from {y:.2f} to {y + slice_thickness:.2f}')
    plt.tight_layout()
    plt.show()
    
    y += slice_thickness
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
Figure
No description has been provided for this image
In [ ]:
 

Some drawbacks of our method¶

  • If several leaves are very close to each other, such that they have hight density at overlapping regions, they may be clustered as a single cluster by DBSCAN. In this case, our shape analysis may fail to identify them as leaf-like clusters. Some other clustering method may be needed to separate these leaves.
  • We currently only identify a flat shape as leaf-like shape. However, some leaves may be curled or rolled, which may not be identified by our method. If we could identify a leaf-shape more specifically, the accuracy of leaf identification could be improved.
  • We did not solve the problem of occluded leaves. Some leaves may be partially occluded by other leaves or branches, leading to incomplete point clouds of these leaves. This may affect the shape analysis and leaf identification. Currently, we only identify the visible parts of these leaves.
In [ ]: